"""
Git备份管理器

负责管理每个数据库配置对应的Git子目录，处理文件差异检查和自动提交推送。
"""

import os
import logging
import shutil
from typing import Dict, List, Any, Optional
from pathlib import Path
import datetime

from .diff_checker import DiffChecker
from .operations import GitOperations


class GitBackupManager:
    """Git备份管理器
    
    负责管理每个数据库配置对应的Git子目录，处理文件差异检查和自动提交推送。
    """
    
    def __init__(self, logger: logging.Logger = None):
        """初始化Git备份管理器
        
        参数:
            logger (logging.Logger): 日志记录器
        """
        self.logger = logger or logging.getLogger(__name__)
        self.diff_checker = DiffChecker(logger)
        self.git_operations = GitOperations(logger)
        
    def setup_git_backup(self, config_name: str, git_base_path: str) -> Dict[str, Any]:
        """设置Git备份环境
        
        为指定的数据库配置创建对应的Git子目录。
        
        参数:
            config_name (str): 配置名称
            git_base_path (str): Git基础路径
            
        返回:
            Dict[str, Any]: 设置结果
        """
        try:
            # 创建配置对应的Git子目录路径
            git_subdir = os.path.join(git_base_path, config_name)
            
            # 初始化Git仓库
            result = self.git_operations.init_repository(git_subdir)
            
            if result.get('success', False):
                self.logger.info(f"Git备份环境设置成功: {git_subdir}")
                return {
                    'success': True,
                    'git_path': git_subdir,
                    'config_name': config_name
                }
            else:
                return result
                
        except Exception as e:
            self.logger.error(f"设置Git备份环境失败: {e}")
            return {
                'success': False,
                'error': str(e)
            }
    
    def process_backup_file(self, config_name: str, backup_file: str, 
                          git_base_path: str) -> Dict[str, Any]:
        """处理备份文件
        
        检查备份文件与Git仓库中文件的差异，有差异则提交并推送。
        
        参数:
            config_name (str): 配置名称
            backup_file (str): 备份文件路径
            git_base_path (str): Git基础路径
            
        返回:
            Dict[str, Any]: 处理结果
        """
        try:
            git_subdir = os.path.join(git_base_path, config_name)
            
            # 检查Git仓库是否存在
            if not os.path.exists(os.path.join(git_subdir, '.git')):
                # 如果Git仓库不存在，先设置环境
                setup_result = self.setup_git_backup(config_name, git_base_path)
                if not setup_result.get('success', False):
                    return setup_result
            
            # 获取备份文件名
            backup_filename = os.path.basename(backup_file)
            git_backup_path = os.path.join(git_subdir, 'backups', backup_filename)
            
            # 确保备份目录存在
            os.makedirs(os.path.dirname(git_backup_path), exist_ok=True)
            
            # 检查文件差异
            diff_result = self.diff_checker.check_file_difference(
                backup_file, git_backup_path
            )
            
            if diff_result.get('has_difference', False):
                # 有差异，复制文件到Git目录
                shutil.copy2(backup_file, git_backup_path)
                
                # 生成提交消息（当前时间）
                commit_message = datetime.datetime.now().strftime("数据库备份 - %Y-%m-%d %H:%M:%S")
                
                # 提交文件
                commit_result = self.git_operations.commit_file(
                    git_subdir, git_backup_path, commit_message
                )
                
                if commit_result.get('success', False):
                    self.logger.info(f"备份文件已提交到Git: {backup_filename}")
                    
                    # 尝试推送（如果配置了远程仓库）
                    push_result = self.git_operations.push_to_remote(git_subdir)
                    
                    return {
                        'success': True,
                        'has_difference': True,
                        'file_committed': True,
                        'commit_hash': commit_result.get('commit_hash'),
                        'commit_message': commit_message,
                        'pushed_to_remote': push_result.get('success', False),
                        'backup_file': backup_file,
                        'git_path': git_subdir
                    }
                else:
                    return commit_result
            else:
                # 没有差异，不需要提交
                self.logger.info(f"备份文件无差异，跳过提交: {backup_filename}")
                return {
                    'success': True,
                    'has_difference': False,
                    'file_committed': False,
                    'backup_file': backup_file,
                    'git_path': git_subdir
                }
                
        except Exception as e:
            self.logger.error(f"处理备份文件失败: {e}")
            return {
                'success': False,
                'error': str(e)
            }
    
    def get_git_status(self, config_name: str, git_base_path: str) -> Dict[str, Any]:
        """获取Git仓库状态
        
        参数:
            config_name (str): 配置名称
            git_base_path (str): Git基础路径
            
        返回:
            Dict[str, Any]: Git仓库状态信息
        """
        try:
            git_subdir = os.path.join(git_base_path, config_name)
            
            if not os.path.exists(os.path.join(git_subdir, '.git')):
                return {
                    'success': False,
                    'error': 'Git仓库不存在',
                    'git_path': git_subdir
                }
            
            return self.git_operations.get_repository_info(git_subdir)
            
        except Exception as e:
            self.logger.error(f"获取Git状态失败: {e}")
            return {
                'success': False,
                'error': str(e)
            }
    
    def cleanup_git_backup(self, config_name: str, git_base_path: str) -> Dict[str, Any]:
        """清理Git备份
        
        参数:
            config_name (str): 配置名称
            git_base_path (str): Git基础路径
            
        返回:
            Dict[str, Any]: 清理结果
        """
        try:
            git_subdir = os.path.join(git_base_path, config_name)
            
            if os.path.exists(git_subdir):
                # 这里可以根据需要实现清理逻辑
                # 目前只是返回状态信息
                return {
                    'success': True,
                    'git_path': git_subdir,
                    'cleaned': True
                }
            else:
                return {
                    'success': True,
                    'git_path': git_subdir,
                    'cleaned': False,
                    'message': 'Git目录不存在'
                }
                
        except Exception as e:
            self.logger.error(f"清理Git备份失败: {e}")
            return {
                'success': False,
                'error': str(e)
            }
    
    def cleanup(self) -> None:
        """清理Git备份管理器资源
        
        这个方法用于清理Git备份管理器相关的资源。
        """
        # 清理GitOperations资源
        if hasattr(self, 'git_operations') and self.git_operations:
            self.git_operations.cleanup()
        
        # GitBackupManager类目前没有其他需要特殊清理的资源
        # 这个方法为空实现，保持接口一致性


def create_git_backup_manager(logger: logging.Logger = None) -> GitBackupManager:
    """创建Git备份管理器实例
    
    参数:
        logger (logging.Logger): 日志记录器
        
    返回:
        GitBackupManager: Git备份管理器实例
    """
    return GitBackupManager(logger)